#include "Plane.h"
#include "BoundingVolume.h"

namespace Nezha
{
	Plane::Plane(const Vector3& p0, const Vector3& p1, const Vector3& p2)
	{
		reset(p0, p1, p2);
	}

	void Plane::reset(const Vector3& p0, const Vector3& p1, const Vector3& p2)
	{
		Vector3 e1 = p1 - p0;
		Vector3 e2 = p2 - p0;
		mNormal = e1.unitCross(e2);
		mConstant = -mNormal.dot(p0);
	}

	float Plane::distane2(const Vector3& p) const
	{
		return mNormal.dot(p) + mConstant;
	}

	Plane::Side Plane::whichSide(const Vector3& p) const
	{
		float dis = distane2(p);
		
		if(dis < 0.0f)
			return SIDE_NEGATIVE;
		else if(dis > 0.0f)
			return SIDE_POSITIVE;

		return SIDE_NONE;
	}

	Plane::Side Plane::whichSide(const AABB& aabb) const
	{
		if(aabb.empty() || aabb.notValid())
			return SIDE_NONE;

		return whichSide(aabb.getCenter(), aabb.getSize() * 0.5f);
	}

	Plane::Side Plane::whichSide(const Vector3& center, const Vector3& halfSize) const
	{
		float dis = distane2(center);

		float absDis = abs(mNormal.x * halfSize.x) + abs(mNormal.y * halfSize.y) + abs(mNormal.z * halfSize.z);

		if(dis < -absDis)
			return SIDE_NEGATIVE;
		else if(dis > absDis)
			return SIDE_POSITIVE;

		return SIDE_BOTH;
	}
}